<?php
/**
 * LowCalVanilla Functions
 *
 * @author @@AUTHOR@@
 * @copyright @@AUTHOR@@ @@YEAR@@
 * @version @@VERSION@@
 * @package Extensions
 * @subpackage Low-Cal_Vanilla
 * @license  @@LICENCE_URL@@ @@LICENCE@@
 *
 * $Id: Functions.php 337 2008-11-03 10:44:38Z dinoboff $
 * $HeadURL$
 */

if (!defined('IN_VANILLA')) exit();

require_once($Configuration['LIBRARY_PATH'] . 'Framework/Framework.Functions.php');
require_once('Class.MergedFiles.php');
require_once('Class.File.php');

/**
 * Check the client can receive gz encoded content
 * @return bool
 */
function LowCalVanilla_AcceptGzip($Configuration) {
	if ( $Configuration['LOWCALVANILLA_GZIP_ALLOWED']
	  && !LowCalVanilla_IsGzipIncompatibleClient()
	  && !empty($_SERVER['HTTP_ACCEPT_ENCODING'])
	  && preg_match('/gzip/', $_SERVER['HTTP_ACCEPT_ENCODING'])
	) {
		return true;
	} else {
		return false;
	}
}

/**
 * Set the LowCalVanilla_MergeFiles to serve.
 * @return LowCalVanilla_MergeFiles
 */
function LowCalVanilla_GetFilesToMerge(&$Context) {
	$LowCalVanilla_FileList = array();
	include($Context->Configuration['LOWCALVANILLA_CONF_DIR'] . 'FileList.php');

	$MineTypes = array(
		'js' => 'text/javascript',
		'css' => 'text/css'
	);

	$Type = ForceIncomingString('type', 'js');
	if (isset($MineTypes[$Type])) {
		$Mime = $MineTypes[$Type];
	}

	$Files = array();
	$IncomingFileList = ForceIncomingArray('f', array());
	foreach ($IncomingFileList as $key) {
		if (isset($LowCalVanilla_FileList[$key])) {
			$file = new LowCalVanilla_File(
				$Context,
				$Context->Configuration['APPLICATION_PATH']
				.  $LowCalVanilla_FileList[$key]);
			if ($file->Exist()) {
				$Files[] = $file;
			} else {
				$Context->WarningCollector->Add(
					$LowCalVanilla_FileList[$key] . ' could not be found.');
			}
		}
	}

	if (count($Files) > 0) {
		return new LowCalVanilla_MergedFile($Context, $Files, $Mime);
	} else {
		return false;
	}
}

/**
 * Add a path to the list of file
 * @return bool
 * @param string|array $Path
 */
function LowCalVanilla_AddScriptToList($Context, $ArrayPaths) {
	$FileList = new LowCalVanilla_File($Context,
		$Context->Configuration['LOWCALVANILLA_CONF_DIR']
		. '/FileList.php');
	if (!$FileList->Exist()
		|| !$FileList->IsWritable()
	) {
		return false;
	}
	$FileList->Open('ab');
	foreach ($ArrayPaths as $path) {
		if (is_string($path)
			&& preg_match('/^[\/\.-_~a-zA-Z0-9]+$/', $path)
		) {
			$FileList->Write('
$LowCalVanilla_FileList[] = \'' . $path . "' ;\n");
		}
	}
	$FileList->Close();
	return true;
}

/**
 * Update the list of script to pack
 * @return void
 * @param array $Scripts The function will check these scripts are in the list
 */
function LowCalVanilla_UpdateScriptList($Context, $Scripts) {
	$LowCalVanilla_FileList = array();
	include($Context->Configuration['LOWCALVANILLA_CONF_DIR'] . 'FileList.php');

	$FileToAdd = array();

	foreach ($Scripts as $file) {
		if (!in_array($file, $LowCalVanilla_FileList)) {
			$FileToAdd[] = $file;
		}
	}

	if (count($FileToAdd) > 0) {
		return LowCalVanilla_AddScriptToList($Context, $FileToAdd);
	} else {
		return null;
	}
}

/**
 * Remove the 4 core js file in Head::Scripts
 * @return void
 */
function LowCalVanilla_PackJsFiles(&$Head) {

	$ScriptRoot = $Head->Context->Configuration['WEB_ROOT'];
	$LowCalVanillaRoot = $Head->Context->Configuration['LOWCALVANILLA_ROOT'];

	// Script to pack for this page
	$FileToPack = array('js/global.js');


	// Default script to remove from $Head->Scripts
	$JSPath = array('js/vanilla.js', 'js/ajax.js', 'js/ac.js', 'js/jquery.js', 'js/prototype.js');
	foreach ($JSPath as $path) {
		$ScriptPath = ConcatenatePath($ScriptRoot, $path);
		$key = array_search($ScriptPath, $Head->Scripts);
		if ($key !== false) {
			unset($Head->Scripts[$key]);
			$FileToPack[] = $path;
		}
	}

	// Add Scriptaculous
	$Scriptaculous = ConcatenatePath($ScriptRoot, 'js/scriptaculous.js');
	$key = array_search($Scriptaculous, $Head->Scripts);
	if ($key) {
		unset($Head->Scripts[$key]);
		$FileToPack[] = 'js/builder.js';
		$FileToPack[] = 'js/effects.js';
		$FileToPack[] = 'js/dragdrop.js';
		$FileToPack[] = 'js/controls.js';
		$FileToPack[] = 'js/slider.js';
	}

	// Add extension script
	if (isset($Head->Context->PassThruVars['LOWCALVANILLA_SCRIPTS'])
		&& is_array($Head->Context->PassThruVars['LOWCALVANILLA_SCRIPTS'])
	) {
		ksort($Head->Context->PassThruVars['LOWCALVANILLA_SCRIPTS']);
		$ExtScript = array_values($Head->Context->PassThruVars['LOWCALVANILLA_SCRIPTS']);
		$FileToPack = array_merge($FileToPack, $ExtScript);
	}

	// Update the list of script
	LowCalVanilla_UpdateScriptList($Head->Context, $FileToPack);

	// Load the list of script
	$LowCalVanilla_FileList = array();
	include($Head->Context->Configuration['LOWCALVANILLA_CONF_DIR'] . 'FileList.php');
	$List = array_flip($LowCalVanilla_FileList);

	// Add the packer to $Head->Scripts
	$Packer = ConcatenatePath($LowCalVanillaRoot, 'packer.php');
	$Packer .= '?v='
		. urlencode($Head->Context->Configuration['LOWCALVANILLA_VERSION'])
		.'&amp;type=js';
	foreach ($FileToPack as $file) {
		if (array_key_exists($file, $List)) {
			$Packer .='&amp;f[]=' . $List[$file];
		}
	}

	// Replace in $Head->Script global.js by the packer script
	$GlobalPath = ConcatenatePath($ScriptRoot, 'js/global.js');
	$key = array_search($GlobalPath, $Head->Scripts);
	if ($key !== false) {
		$Head->Scripts[$key] = $Packer;
	} else {
		// if global.js can't be found to be replace
		// add the packer script to $Head->Scripts
		$Head->Scripts = array_merge(array($Packer), $Head->Scripts);
	}

	// Remove holes from $Head->Scripts
	$Head->Scripts = array_values($Head->Scripts);
}

/**
 * Sniff for browser having issue with gzip content.
 * @param bool $ResponseForNoInfo What to return if USER_AGENT is not set
 * @return bool Return true if you cannot believe Accept-Encoding
 * @uses $_SERVER['HTTP_USER_AGENT']
 * @link http://support.microsoft.com/kb/321722/EN-US/
 * @link http://support.microsoft.com/default.aspx?scid=kb;[LN];Q312496
 */
function LowCalVanilla_IsGzipIncompatibleClient($ResponseForNoInfo = true) {

	// return if $_SERVER['HTTP_USER_AGENT'] is not set
	if (empty($_SERVER['HTTP_USER_AGENT'])) {
		return $ResponseForNoInfo;
	}

	/**
	 * Netscape 4.0 and IE6 have some bugs with gzip content evevn if they are supposed to accept it.
	 * Also, gunzip content will always be cached in IE5.5 and IE6
	 */
	$Pattern = '/(Mozilla\/4\.0(?!.*\b(MSIE|opera|safari))|\bMSIE (5\.5|6\.0))/i';
	if (preg_match($Pattern, $_SERVER['HTTP_USER_AGENT'])) {
		return true;
	}
	return false;
}

/**
 * Add Low-Cal vanilla settings to conf/settings.php (no settings yet).
 * @param Context $Context Vanilla context object
 * @return void
 */
function LowCalVanilla_Install(&$Context, $VersionRef, $LowCalVanillaDir) {

	if (array_key_exists('LOWCALVANILLA_VERSION', $Context->Configuration)
		&& version_compare($Context->Configuration['LOWCALVANILLA_VERSION'], '0.5.0', '<')
	) {
		// Compression should be left to Apache
		AddConfigurationSetting($Context, 'LOWCALVANILLA_GZIP_ALLOWED', '0');
	}

	if (!array_key_exists('LOWCALVANILLA_VERSION', $Context->Configuration)
		|| version_compare($Context->Configuration['LOWCALVANILLA_VERSION'], $VersionRef, '<')
	) {
		$LowCalVanillaDir = str_replace('\\', '/',$LowCalVanillaDir);
		$Config = array(
			'LOWCALVANILLA_GZIP_ALLOWED'	=> '0',
			'LOWCALVANILLA_PACKER_ENABLE' 	=> '1',
			'LOWCALVANILLA_PACKER_COMPRESSION_ENABLE' 	=> '0',
			'LOWCALVANILLA_EXPIRE' 			=> '30758400',
			'LOWCALVANILLA_DIR'				=> $LowCalVanillaDir,
			'LOWCALVANILLA_CONF_DIR'		=> $LowCalVanillaDir . '/conf/',
			'LOWCALVANILLA_ROOT'			=> $Context->Configuration['WEB_ROOT'] . 'extensions/LowCalVanilla/',
			'LOWCALVANILLA_CACHE_DIR'		=> $LowCalVanillaDir . '/cache/',
			'LOWCALVANILLA_TOOLS_PATH'		=> $LowCalVanillaDir . '/tools/utilities.php',
			'LOWCALVANILLA_CACHE_EXT'		=> '.cache'
		);
		foreach ($Config as $key => $value) {
			if (!array_key_exists($key, $Context->Configuration)) {
				AddConfigurationSetting($Context, $key, $value);
			}
		}

		AddConfigurationSetting($Context, 'LOWCALVANILLA_VERSION', $VersionRef);
	}
}
